package com.rui.study.algorithm.L_算法与数据结构_队列_数组实现;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

/**
 * @program: study
 * @description:
 * @author: Yaowr
 * @create: 2019-03-08 08:34
 **/
public class Queue {

    public static final Logger LOGGER = LoggerFactory.getLogger(Queue.class);

    private Node[] elements;

    private int head;
    private int tail;


    public Queue(int size) {
        this.elements = new Node[size];
        head = 0;
        tail = 0;
    }

    /**
     * 入队：入队成功，立即返回true；入队失败，立即返回false
     * @param node
     * @return
     */
    public boolean enqueue(Node node) {
        if (tail < elements.length) {
            if (tail == head && elements[tail] != null) {
                LOGGER.debug("队列已满");
                return false;
            }
            elements[tail] = node;
            tail = tail + 1 < elements.length ? tail + 1 : 0;
            return true;
        }
        return false;
    }

    /**
     * 出队：如果队列为空返回null
     * @return
     */
    public Node dequeue() {
        if (head == tail && elements[head] == null) {
            LOGGER.debug("队列为空");
            return null;
        }
        Node r = elements[head];
        elements[head] = null;
        head = head + 1 < elements.length ? head + 1 : 0;
        return r;
    }

    public static class Node<T extends Worker> {
        T worker;

        public Node(T worker) {
            this.worker = worker;
        }
    }


    public interface Worker {
        void work();
    }

    public static abstract class AbstracWorker implements Worker {

        public static final Logger LOGGER = LoggerFactory.getLogger(AbstracWorker.class);

        int start;
        int end;

        public AbstracWorker(int start, int end) {
            this.start = start;
            this.end = end;
        }

        @Override
        public void work() {
            for (int i = start; i < end; i++) {
                LOGGER.debug((String) doWork(i));
            }
        }

        protected abstract Object doWork(int i);
    }

    public static class SimpleWorker extends AbstracWorker {

        public SimpleWorker(int start, int end) {
            super(start, end);
        }

        @Override
        protected Object doWork(int i) {
            return "账单计算：" + i;
        }
    }

}
